# -*- coding: utf-8 -*-
"""
    时间转时间戳

"""
import time
from datetime import timedelta
from pytz import timezone, utc
import pytz
import datetime

TIME_ZONE = 'Asia/Shanghai'
TZ = pytz.timezone(TIME_ZONE)
FORMATTER = "%Y-%m-%d %H:%M:%S"


class TimeConvert(object):
    """
        时间处理工具类
    """

    def now_ts(self) -> int:
        """
        当前时间戳（秒）
        """
        return int(time.time())

    def now_ts_ms(self) -> int:
        """
        当前时间戳（毫秒）
        """
        return int(time.time() * 1000)

    def now_dt(self) -> datetime.datetime:
        dt = datetime.datetime.now()
        return self.convert_dt_by_tz(dt)

    def convert_dt_by_tz(dt: datetime.datetime, target_tz=TZ) -> datetime.datetime:
        """ 将datetime转换为指定时区 """
        target_dt = dt.astimezone(target_tz)
        return target_dt

    def str2ts(date_str: str, fmt: str = FORMATTER, zone: str = TIME_ZONE) -> int:
        """
        将时间字符串转换为时间戳（毫秒）
        """
        try:
            dt = datetime.datetime.strptime(date_str, fmt)
            tz = timezone(zone)
            localized_dt = tz.localize(dt)
            ts = int(localized_dt.timestamp() * 1000)
            return ts
        except Exception:
            return 0

    def ts2str(self, timestamp: int, fmt: str = FORMATTER, zone: str = TIME_ZONE) -> str:
        """
        将时间戳（秒或毫秒）转换为时间字符串
        """
        if len(str(timestamp)) == 13:
            timestamp = timestamp // 1000
        tz = timezone(zone)
        dt = datetime.datetime.fromtimestamp(timestamp, tz)
        return dt.strftime(fmt)

    def ts2dt(self, ts: int) -> datetime.datetime:
        if len(str(ts)) == 13:
            ts = ts // 1000
        return pytz.datetime.datetime.fromtimestamp(ts, pytz.utc).astimezone(TZ)

    def dt2ts(self, dt: datetime.datetime) -> int:
        """
            将 datetime 转换为时间戳（秒）
        """
        if dt is not None:
            return int(dt.timestamp())

    def dt2str(self, dt: datetime.datetime, fmt: str = FORMATTER) -> str:
        """
            将 datetime 转换为字符串
        """
        if dt is not None:
            return self.convert_dt_by_tz(dt).strftime(fmt)

    def str2dt(self, dt_str: str, fmt: str = FORMATTER) -> datetime.datetime:
        dt = datetime.datetime.strptime(dt_str, fmt)
        return self.convert_dt_by_tz(dt)

    def date_range(start_date: datetime.datetime, n: int) -> list:
        """
        从指定开始时间，生成长度为 n 的时间序列（每分钟递增）
        """
        return [start_date + timedelta(minutes=i) for i in range(n)]

    def round_datetime(dt: datetime.datetime, scale: str = "second") -> datetime.datetime:
        """
        将 datetime 向下取整到指定单位（second/minute/hour）
        """
        if scale == "second":
            return dt.replace(microsecond=0)
        elif scale == "minute":
            return dt.replace(second=0, microsecond=0)
        elif scale == "hour":
            return dt.replace(minute=0, second=0, microsecond=0)
        else:
            return dt
